package com.mz.mattress.admin.service.impl;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.mz.mattress.admin.api.req.CardQueryReq;
import com.mz.mattress.admin.mapper.*;
import com.mz.mattress.admin.service.CardService;
import com.mz.mattress.api.common.Result;
import com.mz.mattress.api.entity.Card;
import com.mz.mattress.api.entity.CardBlack;
import com.mz.mattress.api.entity.CardMerchant;
import com.mz.mattress.api.entity.Merchant;
import com.mz.mattress.api.util.StringTools;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.time.LocalDate;
import java.util.*;

@Slf4j
@Service
public class CardServiceImpl implements CardService {

    @Autowired
    private CardMapper cardMapper;

    @Autowired
    private CardMerchantMapper cardMerchantMapper;

    @Autowired
    private BlackItemMapper blackItemMapper;

    @Autowired
    private CardBlackMapper cardBlackMapper;

    @Autowired
    private MerchantMapper merchantMapper;

    @Override
    public Result<IPage<Card>> listPage(CardQueryReq req) {
        Page<Card> listPage = cardMapper.listPage(req.newPage(), req.getMerchantId(), req.getState(), req.getName(), null);
        return Result.ok(listPage);
    }

    @Override
    public Result<Card> getById(Integer id) {
        Card card = cardMapper.selectById(id);
        if (card == null) {
            return Result.fail("找不到广告");
        }

        List<CardMerchant> list = cardMerchantMapper.selectByCardId(id);
        card.setMerchantList(list);

//        List<Integer> blackIds = cardBlackMapper.selectIdByCardId(id);
//        card.setBlackIds(blackIds);

//        List<Integer> merchantIds = card.getMerchantIds();
//
//        if (merchantIds.size() > 0) {
//
//            List<MerchantVo> merchantVos = merchantMapper.selectByIds(merchantIds);
//            List<CardMerchant> list = new ArrayList<>();
//            for (MerchantVo vo : merchantVos) {
//                CardMerchant cardMerchant = new CardMerchant();
//                cardMerchant.setCardId(id);
//                cardMerchant.setMerchantId(vo.getId());
//                cardMerchant.setMerchantName(vo.getName());
//                list.add(cardMerchant);
//            }
//            card.setMerchantList(list);
//        }

        return Result.ok(card);
    }

    @Override
    public Result add(Card card) {

        if (card.getStartDate() == null || card.getEndDate() == null || card.getSendRule() == null) {
            return Result.fail("参数错误");
        }

        LocalDate start = LocalDate.parse(card.getStartDate());
        LocalDate end = LocalDate.parse(card.getEndDate());
        if (start.isAfter(end)) {
            return Result.fail("开始日期应早于结束日期");
        }

        Merchant merchant = merchantMapper.selectById(card.getMerchantId());
        if (merchant == null) {
            return Result.fail("找不到商家");
        }

        card.setMerchantName(merchant.getName());
        card.setProvince(merchant.getProvince());
        card.setCity(merchant.getCity());

        LocalDate now = LocalDate.now();
        if (now.isBefore(start)) {
            card.setStatus(0);
        } else if (now.isAfter(end)) {
            card.setStatus(2);
        } else {
            card.setStatus(1);
        }

        cardMapper.insert(card);

        for (Integer merchantId : card.getMerchantIds()) {
            CardMerchant cardMerchant = new CardMerchant();
            cardMerchant.setMerchantId(merchantId);
            cardMerchant.setCardId(card.getId());
            cardMerchantMapper.insert(cardMerchant);
        }

        if (card.getMerchantIds().size() > 0) {
            //更新商家名称
            cardMerchantMapper.updateMerchantNameIsNull();
        }

        List<Integer> blackIds = card.getBlackIds();

        if (blackIds != null && blackIds.size() > 0) {

            HashSet<String> sets = new HashSet<>();

            for (Integer blackId : blackIds) {

                List<String> list = blackItemMapper.list(blackId);
                sets.addAll(list);

            }

            for (String mobile : sets) {

                CardBlack cardBlack = new CardBlack();
                cardBlack.setCardId(card.getId());
                cardBlack.setMobile(mobile);
                cardBlackMapper.insert(cardBlack);

            }

        }

        Integer count = cardBlackMapper.selectCountByCardId(card.getId());
        Card update = new Card();
        update.setId(card.getId());
        update.setBlackCount(count);
        update.setBlackGroupIds(StringTools.join(blackIds, ","));
        cardMapper.updateById(update);

        return Result.ok();
    }

    @Override
    public Result stop(Integer id) {

        Card card = cardMapper.selectById(id);
        if (card == null) {
            return Result.fail();
        }

        Card update = new Card();
        update.setId(id);
        update.setStatus(2);
        cardMapper.updateById(update);

        return Result.ok();
    }

    @Override
    public Result updateById(Card card) {

        if (card.getStartDate() == null || card.getEndDate() == null) {
            return Result.fail("参数错误");
        }

        LocalDate start = LocalDate.parse(card.getStartDate());
        LocalDate end = LocalDate.parse(card.getEndDate());
        if (start.isAfter(end)) {
            return Result.fail("开始日期应早于结束日期");
        }

        LocalDate now = LocalDate.now();
        if (now.isBefore(start)) {
            card.setStatus(0);
        } else if (now.isAfter(end)) {
            card.setStatus(2);
        } else {
            card.setStatus(1);
        }

        cardMapper.updateById(card);

//        List<CardMerchant> list = cardMerchantMapper.selectByCardId(card.getId());
        List<Integer> list = cardMerchantMapper.selectMerchantIdByCardId(card.getId());

        if (list.size() > 0) {

//            List<Integer> idList = list.stream().map(a -> a.getMerchantId()).collect(Collectors.toList());

            Map<String, Set<Integer>> map = getDiff(list, card.getMerchantIds());
            Set<Integer> onlyInA = map.get("onlyInA");
            Set<Integer> onlyInB = map.get("onlyInB");

            if (onlyInA.size() > 0) {
                cardMerchantMapper.deleteByMerchantIds(card.getId(), onlyInA);
            }

            for (Integer merchantId : onlyInB) {
                CardMerchant cardMerchant = new CardMerchant();
                cardMerchant.setMerchantId(merchantId);
                cardMerchant.setCardId(card.getId());
                cardMerchantMapper.insert(cardMerchant);
            }

        } else {
            for (Integer merchantId : card.getMerchantIds()) {
                CardMerchant cardMerchant = new CardMerchant();
                cardMerchant.setMerchantId(merchantId);
                cardMerchant.setCardId(card.getId());
                cardMerchantMapper.insert(cardMerchant);
            }
        }

        return Result.ok();
    }

    @Override
    public Result deleteByIds(Set<Integer> ids) {
        cardMapper.deleteBatchIds(ids);
        return Result.ok();
    }

    public static <T> Map<String, Set<T>> getDiff(Collection<T> collectionA,
                                                  Collection<T> collectionB) {
        Set<T> setA = new HashSet<>(collectionA);
        Set<T> setB = new HashSet<>(collectionB);

        Map<String, Set<T>> result = new HashMap<>();

        Set<T> onlyInB = new HashSet<>(setB);
        onlyInB.removeAll(setA);

        Set<T> onlyInA = new HashSet<>(setA);
        onlyInA.removeAll(setB);

        result.put("onlyInA", onlyInA);
        result.put("onlyInB", onlyInB);

        return result;
    }

    public static void main(String[] args) {

        LocalDate parse = LocalDate.parse("2025-10-11");
        System.out.println(parse);


        ArrayList<Integer> list = new ArrayList<>();
        list.add(1);
        list.add(2);
        list.add(3);

        String join = StringTools.join(list, ",");
        System.out.println(join);
    }

}
